òɾۿûѧϰʹá
ԭַhttps://www.joinquant.com/post/11764

ԭһ˵ʽ鵽ԭĺ߽ۡ


ԭĲԴ£

# ¡Ծۿ£https://www.joinquant.com/post/11736
# ⣺_Բԣѧϰԣ
# ߣά

# ¡Ծۿ£https://www.joinquant.com/post/1810
# ⣺áЭİש
# ߣJoinQuant

import numpy as np
import pandas as pd

#===========================================

def initialize(context):
    set_params()
    set_variables()
    set_backtest()

# ---1. ò
def set_params():
    # Ʊ1
    g.security1 = '510220.XSHG' 
    # Ʊ2
    g.security2 = '510500.XSHG'
    # ׼
    g.benchmark = '510500.XSHG'
    # عϵ
    g.regression_ratio = 1#0.9574#0.9938
    # Ʊ1Ĭϲλ
    g.p = 0.5
    # Ʊ2Ĭϲλ
    g.q = 0.5
    # z-score
    g.test_days = 120

# ---2. ñ
def set_variables():
    # ״̬
    g.state = 'empty'

# ---3. ûز
def set_backtest():
    # û׼
    set_benchmark(g.benchmark)
    # ֻ
    log.set_level('order', 'error')
    # ʵ۸
    set_option('use_real_price', True) 
    # ޻
    set_slippage(FixedSlippage(0.))

#==============================================
    
# ÿλʱ(ز,ÿһ,,ÿӵһ)һ
def handle_data(context, data):
    new_state = get_signal()
    change_positions(get_signal(),context)

# ---4.z-score
def z_test():
    # ȡ֧Ʊʷ۸
    prices1 = np.array(attribute_history(g.security1, g.test_days, '1d', 'close'))
    prices2 = np.array(attribute_history(g.security2, g.test_days, '1d', 'close'))
    # ݻعǵƽ Y-a.X
    stable_series = prices2 - g.regression_ratio*prices1
    # ֵ
    series_mean = mean(stable_series)
    # ׼
    sigma = np.std(stable_series)
    # ֵֵ
    diff = stable_series[-1] - series_mean
    # zֵ
    return(diff/sigma)# ֵӱ׼ֲ̫

# ---5.ȡź
# µ״̬һstring
def get_signal():
    z_score = z_test()
    if z_score > 2.1:#/0.82
        # ״̬Ϊȫֵһ֧
        return('buy1')
    # Сڸ׼
    if z_score < -2.1:
        # ״̬Ϊȫֵڶ֧
        return('buy2')
    # ׼֮
    if -1.95<= z_score <= 1.95:
        return('mid')
            
# ---6.źŵλ
# Ŀ״̬Ϊһstring
def change_positions(current_state,context):
    # ֵֵ
    total_value = context.portfolio.portfolio_value
    # ״̬ȫֹƱ1
    if  current_state== 'buy1':
        # ȫƱ2
        #order_target(g.security2, 0)
        marginsec_open(g.security2, 100000, style=None, pindex=0)
        # ȫƱ1
        order_value(g.security1, total_value)
        # ״̬
        g.state = 'buy1'
    # ״̬ȫֹƱ2
    if  current_state == 'buy2':
        # ȫƱ1
        #order_target(g.security1, 0)
        marginsec_open(g.security1, total_value, style=None, pindex=0)
        # ȫƱ2
        order_value(g.security2, total_value)
        # ״̬
        g.state = 'buy2'
    # ȫһƱ״̬z-score0
    if (current_state== 'mid'):
        if(g.state=='buy1'):
            marginsec_close(g.security2, 100000, style=None, pindex=0)
            order_target_value(g.security1, 0)
        if(g.state=='buy2'):
            marginsec_close(g.security1, 100000, style=None, pindex=0)
            order_target_value(g.security2, 0)
        g.state = 'even'


#ֹ